﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Voodoo.TestData.Builders;

namespace Voodoo.TestData
{
    public class RandomDataGenerator
    {
        
        
        public RandomSeedData RandomData { get; set; }
        private Random rnd
        {
            get { return TestHelper.Random; }
        }
        public RandomDataGenerator()
        {
            RandomData = new RandomSeedData();

        }

        public RandomPerson Person()
        {
            return new PersonBuilder().WithAgeRange(AgeRange.Adult).Build(RandomData);
        }
        public RandomAddress Address()
        {
            return new AddressBuilder().Build(RandomData);
        }
        public string Grocery()
        {
            return RandomData.groceries.RandomElement();
        }
        public string GetAdjective()
        {
            return RandomData.adjectives.RandomElement();
        }
        public string GetComment()
        {
            return RandomData.adjectives.RandomElement();
        }
        public int Int(int minVal, int maxVal)
        {
            int num = rnd.Next(minVal, maxVal);
            if (num > maxVal)
                num = maxVal;
            return num;

        }
        public double Double(int minVal, int maxVal)
        {

            double num = rnd.Next(minVal, maxVal);
            num = num + rnd.NextDouble();
            return num;

        }
        public string GibberishText(int lenght)
        {
            Int32 startNum = 97;
            int endNum = 122;
            System.Text.StringBuilder sb = new System.Text.StringBuilder();
            int num = 0;
            for (int i = 0; i <= lenght - 1; i++)
            {
                num = Int(startNum, endNum);
                char c = ((char)num);
                sb.Append(c.ToString());
            }
            string ret = sb.ToString();
            return ret;
        }
        public bool Bool()
        {
            int num = Int(1, 2);
            return num == 1;
        }
        public string TextWithFunkySymbols(int lenght)
        {
            Int32 startNum = 32;
            int endNum = 126;
            System.Text.StringBuilder sb = new System.Text.StringBuilder();
            for (int i = 0; i <= lenght - 1; i++)
            {
                var temp = ((char)Int(startNum, endNum)).ToString();
                while ((temp.Equals(">")) || (temp.Equals("<")))
                {
                    temp = ((char)Int(startNum, endNum)).ToString();
                }
                sb.Append(temp);
            }
            return sb.ToString();
        }
        public string Characters(int lenght)
        {
            int startNum = 32;
            int endNum = 47;
            System.Text.StringBuilder sb = new System.Text.StringBuilder();
            for (int i = 0; i <= lenght - 1; i++)
            {
                var temp = ((char)Int(startNum, endNum)).ToString();
                while ((temp.Equals(">")) || (temp.Equals("<")))
                {
                    temp = ((char)Int(startNum, endNum)).ToString();
                }
                sb.Append(temp);
            }
            return sb.ToString();
        }
        public string NumericString(int length)
        {
            string toReturn = string.Empty;
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < length; i++)
            {
                sb.Append(Int(0, 9).ToString());
            }
            toReturn = sb.ToString();
            return toReturn;
        }
        public DateTime Date(DateTime minDate, DateTime maxDate)
        {
            TimeSpan ts = maxDate.Subtract(minDate);
            int num = Int(0, ts.Days);
            return minDate.AddDays(num);
        }
        public DateTime RecentDate()
        {
            return Date(DateTime.Now.AddMonths(-3), DateTime.Now);
        }
        public DateTime DateNowPlusOrMinusOneMonth()
        {
            return Date(DateTime.Now.AddMonths(-1), DateTime.Now.AddMonths(1));
        }
        public string PhoneNumber(bool includeAreaCode)
        {
            string PhoneNumber = "";
            if (includeAreaCode)
                PhoneNumber += Int(2, 9).ToString() + NumericString(2);
            PhoneNumber += Int(1, 9).ToString() + NumericString(6);
            return PhoneNumber;
        }
        public string Text(int minLength = 0, int maxLength = int.MaxValue)
        {
            var query = RandomData.comments.AsQueryable();
            if (minLength != 0)
                query = query.Where(c => c.Length >= minLength);
            if (maxLength != int.MaxValue)
                query = query.Where(c => c.Length <= maxLength);

            query = query.OrderBy(c => Guid.NewGuid());

            var result = query.FirstOrDefault();
            if (result == null)
                return LoremIpssum(minLength, maxLength);
            else
                return result;
        }

        public string LoremIpssum(int minLength = 0, int maxLength = int.MaxValue)
        {
            //TODO: jumble
            var min = minLength;
            if (min == 0)
                min = 20;

            var max = maxLength;
            var lorem = RandomData.LoremIpsum.Length;
            if (max >= lorem)
                max = lorem;

            if (maxLength == int.MaxValue)
                max = TestHelper.Data.Int(min, max);

            var result = RandomData.LoremIpsum.Substring(0, max);
            return result;



        }
        internal PersonBuilder PersonBuilder()
        {
            return new PersonBuilder();
        }

        internal AddressBuilder AddressBuilder()
        {
            return new AddressBuilder();
        }

        internal Gender RandomGender()
        {
            int num = Int(1, 2);
            return (Gender)Enum.ToObject(typeof(Gender), num);
        }
        internal AgeRange RandomAgeRange()
        {
            int num = Int(1, 2);
            return (AgeRange)Enum.ToObject(typeof(AgeRange), num);
        }
    }
}
